using System;
using System.Collections;
#if !PocketPC || Framework20
using Microsoft.Win32;
#endif

namespace GeoFramework.IO.Bluetooth
{
	/// <summary>
	/// Represents a Bluetooth Radio device.
	/// </summary>
	/// <remarks>Allows you to query properties of the radio hardware and set the mode.</remarks>
	internal sealed class BluetoothRadio
	{
		//handle (xp only)
		private IntPtr m_handle;
		private BLUETOOTH_RADIO_INFO m_radio;

		internal BluetoothRadio(IntPtr handle)
		{
			if(!IsSupported)
				return;

#if PocketPC
			if(System.Environment.OSVersion.Platform != PlatformID.WinCE)
			{
#endif
				m_radio = new BLUETOOTH_RADIO_INFO();
				int hresult = NativeMethods.BluetoothGetRadioInfo(handle, m_radio.ToByteArray());
#if PocketPC
			}
#endif
			m_handle = handle;
		}

		#region Primary Radio
		/// <summary>
		/// Gets the primary BluetoothRadio.
		/// </summary>
		/// <remarks>For devices this is the only BluetoothRadio, for Windows XP this is the first available BluetoothRadio device.</remarks>
		public static BluetoothRadio PrimaryRadio
		{
			get
			{
#if PocketPC
				if(System.Environment.OSVersion.Platform == PlatformID.WinCE)
				{
					return new BluetoothRadio(IntPtr.Zero);
				}
				else
				{
#endif
					//get a single radio
					IntPtr handle = IntPtr.Zero;
					IntPtr findhandle = IntPtr.Zero;

					BLUETOOTH_FIND_RADIO_PARAMS bfrp;
					bfrp.dwSize = 4;

					findhandle = NativeMethods.BluetoothFindFirstRadio(ref bfrp, ref handle);
				
					if(findhandle!=IntPtr.Zero)
					{
						NativeMethods.BluetoothFindRadioClose(findhandle);
					}
					return new BluetoothRadio(handle);
#if PocketPC
				}
#endif
			}
		}
		#endregion

		#region All Radios
		/// <summary>
		///  Gets an array of all radios on the system.  
		/// </summary>
//        public static BluetoothRadio[] AllRadios
//        {
//            get
//            {
//#if PocketPC
//                if(System.Environment.OSVersion.Platform == PlatformID.WinCE)
//                {
//                    return new BluetoothRadio[]{new BluetoothRadio(IntPtr.Zero)};
//                }
//#endif

//                IntPtr handle = IntPtr.Zero;
//                IntPtr findhandle = IntPtr.Zero;

//                BLUETOOTH_FIND_RADIO_PARAMS bfrp;
//                bfrp.dwSize = 4;

//                ArrayList radiocollection = new ArrayList();

//                findhandle = NativeMethods.BluetoothFindFirstRadio(ref bfrp, ref handle);
				
//                if(findhandle!=IntPtr.Zero)
//                {		
//                    radiocollection.Add(handle);

//                    while(NativeMethods.BluetoothFindNextRadio(findhandle, ref handle))
//                    {
//                        radiocollection.Add(handle);
//                    }

//                    NativeMethods.BluetoothFindRadioClose(findhandle);
//                }
//                BluetoothRadio[] results = new BluetoothRadio[radiocollection.Count];
//                for(int radioindex = 0; radioindex < results.Length; radioindex++)
//                {
//                    results[radioindex] = new BluetoothRadio((IntPtr)radiocollection[radioindex]);
//                }

//                return results;
//            }
//        }
		#endregion

		public static bool IsSupported
		{
			get
			{
                RegistryKey Microsoft = null;
                try
                {
                    // Look for a registry key
                    Microsoft = Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Microsoft\Bluetooth", false);
                    return Microsoft != null;
                }
                catch
                {
                    return false;
                }
                finally
                {
                    if(Microsoft != null)
                        Microsoft.Close();
                }
			}
		}

		#region Mode
		/// <summary>
		/// Gets or Sets the current mode of operation of the Bluetooth radio.
		/// </summary>
		/// <remarks>This setting will be persisted when the device is reset.
		/// An Icon will be displayed in the tray on the Home screen and the device will emit a blue LED when Bluetooth is enabled.</remarks>
		public RadioMode Mode
		{
			get
			{
#if PocketPC
				if(System.Environment.OSVersion.Platform==PlatformID.WinCE)
				{
					RadioMode val = RadioMode.PowerOff;
					int result = NativeMethods.BthGetMode(ref val);
					if(result!=0)
					{
						throw new System.ComponentModel.Win32Exception(result, "Error getting BluetoothRadio mode");
					}
					return val;
				}
				else
				{
#endif
					if(NativeMethods.BluetoothIsDiscoverable(m_handle))
					{
						return RadioMode.Discoverable;
					}
					if(NativeMethods.BluetoothIsConnectable(m_handle))
					{
						return RadioMode.Connectable;
					}
					return RadioMode.PowerOff;
#if PocketPC
				}
#endif
			}
			set
			{
				if(!IsSupported)
					throw new NotSupportedException();

#if PocketPC
				if(System.Environment.OSVersion.Platform == PlatformID.WinCE)
				{
					int result = NativeMethods.BthSetMode(value);
					if(result!=0)
					{
						throw new System.ComponentModel.Win32Exception(result, "Error setting BluetoothRadio mode");
					}
				}
				else
				{
#endif
					switch(value)
					{
						case RadioMode.Discoverable:
							if(Mode==RadioMode.PowerOff)
							{
								NativeMethods.BluetoothEnableIncomingConnections(m_handle, true);
							}
							NativeMethods.BluetoothEnableDiscovery(m_handle, true);
							break;
						case RadioMode.Connectable:
							if(Mode==RadioMode.Discoverable)
							{
								NativeMethods.BluetoothEnableDiscovery(m_handle, false);
							}
							else
							{
								NativeMethods.BluetoothEnableIncomingConnections(m_handle, true);
							}
							break;
						case RadioMode.PowerOff:
							if(Mode==RadioMode.Discoverable)
							{
								NativeMethods.BluetoothEnableDiscovery(m_handle, false);
							}
							NativeMethods.BluetoothEnableIncomingConnections(m_handle, false);
							break;
					}
#if PocketPC
				}
#endif
			}
		}
		#endregion

		#region Local Address
		/// <summary>
		/// Returns the address of the local Bluetooth radio device.
		/// </summary>
//        public BluetoothAddress LocalAddress
//        {
//            get
//            {
//#if PocketPC
//                if(System.Environment.OSVersion.Platform == PlatformID.WinCE)
//                {
//                    BluetoothAddress ba = new BluetoothAddress();

//                    int result = NativeMethods.BthReadLocalAddr(ba.ToByteArray());

//                    if(result != 0)
//                    {
//                        throw new System.ComponentModel.Win32Exception(result, "Error retrieving local Bluetooth address");
//                    }

//                    return ba;
//                }
//                else
//                {
//#endif
//                    return m_radio.Address;
//#if PocketPC
//                }
//#endif
//            }
//        }
		
		#endregion

		#region Class Of Device
		/// <summary>
		/// Returns the Class of Device.
		/// </summary>
//        public ClassOfDevice ClassOfDevice
//        {
//            get
//            {
//#if PocketPC
//                if(System.Environment.OSVersion.Platform == PlatformID.WinCE)
//                {
//                    uint cod = 0;
//                    int hresult = NativeMethods.BthReadCOD(ref cod);
//                    return (ClassOfDevice)cod;
//                }
//                else
//                {
//#endif
//                    return m_radio.ClassOfDevice;
//#if PocketPC
//                }
//#endif
//            }
//        }
		#endregion

		#region Name
		/*
		/// <summary>
		/// Returns the friendly name of the Bluetooth radio.
		/// </summary>
		public string Name
		{
			get
			{
				if(System.Environment.OSVersion.Platform!=PlatformID.WinCE)
				{
					return m_radio.Name;
				}
				else
				{
					throw new PlatformNotSupportedException();
				}
			}
		}*/
		#endregion


		#region Manufacturer
		/*
		/// <summary>
		/// Returns the manufacturer of the <see cref="BluetoothRadio"/> device.
		/// </summary>
		public Manufacturer Manufacturer
		{
			get
			{
				if(System.Environment.OSVersion.Platform!=PlatformID.WinCE)
				{
					return m_radio.Manufacturer;
				}
				else
				{
					throw new PlatformNotSupportedException();
				}
			}
		}*/
		#endregion
	}
}
